package com.yycx.module.user.provider.service.impl;

import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import com.yycx.common.constants.CommonConstants;
import com.yycx.common.mybatis.base.service.impl.BaseServiceImpl;
import com.yycx.common.base.entity.EntityMap;
import com.yycx.common.mybatis.callback.CriteriaQueryCallBack;
import com.yycx.common.mybatis.model.ResultBody;
import com.yycx.common.mybatis.query.CriteriaQuery;
import com.yycx.common.mybatis.query.CriteriaSave;
import com.yycx.common.utils.ApiAssert;
import com.yycx.common.base.utils.FlymeUtils;
import com.yycx.module.user.client.entity.AppSchool;
import com.yycx.module.user.provider.mapper.SysHtmlMapper;
import com.yycx.module.user.client.entity.SysHtml;
import com.yycx.module.user.provider.service.SysHtmlService;
import io.swagger.models.auth.In;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Propagation;
import org.springframework.transaction.annotation.Transactional;

import java.util.ArrayList;
import java.util.List;
import java.util.Map;

/**
 * 服务协议 实现类
 *
 * @author flyme
 * @date 2019-07-13
 */
@Service
public class SysHtmlServiceImpl extends BaseServiceImpl<SysHtmlMapper, SysHtml> implements SysHtmlService {


    @Override
    public SysHtml findByCode(String htmlCode) {
        QueryWrapper queryWrapper = new QueryWrapper<SysHtml>();
        queryWrapper.eq("htmlCode", htmlCode);
        return getOne(queryWrapper);
    }

    @Override
    public SysHtml findByCodeOrId(String htmlCode) {
        QueryWrapper<SysHtml> queryWrapper = new QueryWrapper<SysHtml>();
        queryWrapper.eq("htmlCode", htmlCode);
        queryWrapper.or().eq("htmlId", htmlCode);
        return getOne(queryWrapper);
    }

    @Override
    public List<EntityMap> listByHtmlType(Integer htmlType, Integer htmlGroup) {
        return listByHtmlType(htmlType, htmlGroup, null);
    }

    @Override
    public List<EntityMap> listByHtmlType(Integer htmlType, Integer htmlGroup, CriteriaQueryCallBack cqc) {
        CriteriaQuery<SysHtml> cq = new CriteriaQuery(SysHtml.class);
        if (FlymeUtils.isNotEmpty(cqc)) {
            cqc.init(cq);
        }
        cq.eq(SysHtml.class, "htmlStatus", CommonConstants.ENABLED);
        cq.eq(SysHtml.class, "htmlType", htmlType);
        cq.eq(SysHtml.class, "htmlGroup", htmlGroup);
        return selectEntityMap(cq);
    }

    @Override
    public EntityMap findByHtmlCode(String htmlCode, Integer htmlGroup, CriteriaQueryCallBack cqc) {
        CriteriaQuery<SysHtml> cq = new CriteriaQuery(SysHtml.class);
        if (FlymeUtils.isNotEmpty(cqc)) {
            cqc.init(cq);
        } else {
            cq.select(SysHtml.class, "htmlId", "htmlTitle", "htmlContent", "htmlGroup", "jumpType", "htmlImage");
        }
        cq.eq(SysHtml.class, "htmlType", CommonConstants.INT_1);
        if (FlymeUtils.isNotEmpty(htmlGroup)) {
            cq.eq(SysHtml.class, "htmlGroup", htmlGroup);
        }
        cq.eq(SysHtml.class, "htmlCode", htmlCode);
        cq.eq(SysHtml.class, "htmlStatus", CommonConstants.ENABLED);
        return findOne(cq);
    }

    @Override
    public EntityMap findByHtmlCode(String htmlCode) {
        return findByHtmlCode(htmlCode, null, null);
    }

    @Override
    public EntityMap findByHtmlCode(String htmlCode, Boolean hasChild) {
        EntityMap entityMap = findByHtmlCode(htmlCode, null, null);
        Long parentId = entityMap.getLong("htmlId");
        List<SysHtml> list=listByParentId(parentId);
        entityMap.put("children", list);
        return entityMap;
    }


    @Override
    public ResultBody beforeListEntityMap(CriteriaQuery<SysHtml> cq, SysHtml sysHtml, EntityMap requestMap) {
        cq.select(SysHtml.class, "htmlId", "parentId", "htmlType", "sortOrder", "htmlGroup", "htmlTitle", "htmlContent");
        cq.eq("parentId", 0);
        cq.eq("htmlGroup", sysHtml.getHtmlGroup());
        return super.beforeListEntityMap(cq, sysHtml, requestMap);
    }

    @Override
    public ResultBody beforeAdd(CriteriaSave cs, SysHtml html, EntityMap extra) {
        Long parentId = FlymeUtils.isEmpty(html.getParentId()) ? 0L : html.getParentId();
        SysHtml parent = getById(parentId);
        long count;
        CriteriaQuery cq = new CriteriaQuery(SysHtml.class);
        if (parentId.equals(0L)) {
            count = count(cq.eq("parentId", cs.getParams("parentId")));
        } else {
            count = count(cq.eq("parentId", parent.getHtmlId()));
        }
        Long sortOrder = FlymeUtils.getLong(count, 0L) + 1;
        html.setParentId(parentId);
        String htmlTitle = html.getHtmlTitle();
        if (FlymeUtils.isEmpty(htmlTitle)) {
            html.setHtmlTitle("分类名称" + sortOrder);
        }
        html.setSortOrder(sortOrder.intValue());
        html.setHtmlStatus(CommonConstants.ENABLED);
        return ResultBody.ok();
    }

    @Override
    public SysHtml getHtml(String htmlTitle) {
        CriteriaQuery<SysHtml> cq = new CriteriaQuery(SysHtml.class);
        cq.eq(true, "htmlTitle", htmlTitle);
        return getOne(cq);
    }


    @Override
    public ResultBody beforeGet(CriteriaQuery<SysHtml> cq, SysHtml sysHtml, EntityMap requestMap) {
        cq.select(SysHtml.class, "*");
        cq.lambda().or(e -> e.eq(true, SysHtml::getHtmlTitle, sysHtml.getHtmlTitle()).or().eq(true, SysHtml::getHtmlCode, sysHtml.getHtmlCode()));
        return super.beforeGet(cq, sysHtml, requestMap);
    }

    private List<SysHtml> listByParentId(Long parentId) {
        CriteriaQuery<SysHtml> cq = new CriteriaQuery(SysHtml.class);
        cq.eq(true, "parentId", parentId);
        cq.orderByAsc("sortOrder");
        return list(cq);
    }

    @Override
    @Transactional(propagation = Propagation.SUPPORTS, readOnly = true)
    public ResultBody selectAllHtml() {
        CriteriaQuery cq = new CriteriaQuery(SysHtml.class);
        cq.select(SysHtml.class, "*");
        cq.orderByAsc("sortOrder");
        List<EntityMap> allList = selectEntityMap(cq);
        return ResultBody.ok(allList);
    }

    /**
     * 递归构建
     *
     * @param list
     * @param parentId
     * @return
     */
    private static List<EntityMap> buildTree(List<EntityMap> list, Long parentId) {
        List<EntityMap> result = new ArrayList();
        list.forEach(category -> {
            Long categoryId = category.getLong("htmlId");
            Long pid = category.getLong("parentId");
            if (parentId.equals(pid)) {
                List child = buildTree(list, categoryId);
                if (parentId.equals(0L)) {
                    category.put("child", child);
                }
                result.add(category);
            }
        });
        return result;
    }
}
